home *** CD-ROM | disk | FTP | other *** search
/ Java Programmer's Toolkit / Java Programmer's Toolkit.iso / solaris2 / jdk / src / java / lang / string.jav < prev    next >
Encoding:
Text File  |  1995-10-30  |  25.4 KB  |  863 lines

  1. /*
  2.  * @(#)String.java    1.51 95/09/27  
  3.  *
  4.  * Copyright (c) 1994 Sun Microsystems, Inc. All Rights Reserved.
  5.  *
  6.  * Permission to use, copy, modify, and distribute this software
  7.  * and its documentation for NON-COMMERCIAL purposes and without
  8.  * fee is hereby granted provided that this copyright notice
  9.  * appears in all copies. Please refer to the file "copyright.html"
  10.  * for further important copyright and licensing information.
  11.  *
  12.  * SUN MAKES NO REPRESENTATIONS OR WARRANTIES ABOUT THE SUITABILITY OF
  13.  * THE SOFTWARE, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
  14.  * TO THE IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
  15.  * PARTICULAR PURPOSE, OR NON-INFRINGEMENT. SUN SHALL NOT BE LIABLE FOR
  16.  * ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING OR
  17.  * DISTRIBUTING THIS SOFTWARE OR ITS DERIVATIVES.
  18.  */
  19.  
  20. package java.lang;
  21.  
  22. import java.util.Hashtable;
  23.  
  24. /**
  25.  * A general class of objects to represent character Strings.
  26.  * Strings are constant, their values cannot be changed after creation.
  27.  * The compiler makes sure that each String constant actually results
  28.  * in a String object. Because String objects are immutable they can
  29.  * be shared. For example:
  30.  * <pre>
  31.  *    String str = "abc";
  32.  * </pre>
  33.  * is equivalent to:
  34.  * <pre>
  35.  *    char data[] = {'a', 'b', 'c'};
  36.  *    String str = new String(data);
  37.  * </pre>
  38.  * Here are some more examples of how strings can be used:
  39.  * <pre>
  40.  *     System.out.println("abc");
  41.  *     String cde = "cde";
  42.  *     System.out.println("abc" + cde);
  43.  *    String c = "abc".substring(2,3);
  44.  *    String d = cde.substring(1, 2);
  45.  * </pre>
  46.  * @see        StringBuffer
  47.  * @version     1.51, 09/27/95
  48.  * @author     Lee Boynton
  49.  * @author    Arthur van Hoff
  50.  */
  51. public final
  52. class String {
  53.     /** The value is used for character storage. */
  54.     private char value[];
  55.  
  56.     /** The offset is the first index of the storage that is used. */
  57.     private int offset;
  58.  
  59.     /** The count is the number of characters in the String. */
  60.     private int count;
  61.  
  62.     /**
  63.      * Constructs a new empty String.
  64.      */
  65.     public String() {
  66.     value = new char[0];
  67.     }
  68.  
  69.     /**
  70.      * Constructs a new String that is a copy of the specified String.
  71.      * @param value the initial value of the String
  72.      */
  73.     public String(String value) {
  74.     count = value.length();
  75.     this.value = new char[count];
  76.     value.getChars(0, count, this.value, 0);
  77.     }
  78.  
  79.     /**
  80.      * Constructs a new String whose initial value is the specified array of characters.
  81.      * The character array is <strong>NOT</strong> copied, so <strong>DO NOT</strong> modify 
  82.      * the array after the String is created!
  83.      * @param value the initial value of the String
  84.      */
  85.     public String(char value[]) {
  86.     this.value = value;
  87.     count = value.length;
  88.     }
  89.  
  90.     /**
  91.      * Constructs a new String whose initial value is the specified sub array of characters.
  92.      * The length of the new string will be count characters
  93.      * starting at offset within the specified character array.
  94.      * The character array is <strong>NOT</strong> copied, so <strong>DO NOT</strong> modify
  95.      * the array after the String is created! 
  96.      * @param value    the initial value of the String, an array of characters
  97.      * @param offset    the offset into the value of the String
  98.      * @param count     the length of the value of the String
  99.      * @exception StringIndexOutOfBoundsException If the offset and count arguments are invalid.
  100.      */
  101.     public String(char value[], int offset, int count) {
  102.     if (offset < 0) {
  103.         throw new StringIndexOutOfBoundsException(offset);
  104.     }
  105.     if (count < 0) {
  106.         throw new StringIndexOutOfBoundsException(count);
  107.     }
  108.     if (offset + count > value.length) {
  109.         throw new StringIndexOutOfBoundsException(offset + count);
  110.     }
  111.  
  112.     this.value = value;
  113.     this.offset = offset;
  114.     this.count = count;
  115.     }
  116.  
  117.     /**
  118.      * Constructs a new String whose initial value is the specified sub array of bytes.
  119.      * The high-byte of each character can be specified, it should usually be 0.
  120.      * The length of the new String will be count characters
  121.      * starting at offset within the specified character array.  
  122.      * @param ascii    the bytes that will be converted to characters
  123.      * @param hibyte    the high byte of each Unicode character
  124.      * @param offset    the offset into the ascii array
  125.      * @param count     the length of the String
  126.      * @exception StringIndexOutOfBoundsException If the offset and count arguments are invalid.
  127.      */
  128.     public String(byte ascii[], int hibyte, int offset, int count) {
  129.     if (offset < 0) {
  130.         throw new StringIndexOutOfBoundsException(offset);
  131.     }
  132.     if (count < 0) {
  133.         throw new StringIndexOutOfBoundsException(count);
  134.     }
  135.     if (offset + count > ascii.length) {
  136.         throw new StringIndexOutOfBoundsException(offset + count);
  137.     }
  138.  
  139.     char value[] = new char[count];
  140.     this.count = count;
  141.     this.value = value;
  142.  
  143.     if (hibyte == 0) {
  144.         for (int i = count ; i-- > 0 ;) {
  145.         value[i] = (char) (ascii[i + offset] & 0xff);
  146.         }
  147.     } else {
  148.         hibyte <<= 8;
  149.         for (int i = count ; i-- > 0 ;) {
  150.         value[i] = (char) (hibyte | (ascii[i + offset] & 0xff));
  151.         }
  152.     }
  153.     }
  154.  
  155.     /**
  156.      * Constructs a new String whose initial value is the specified array of bytes.
  157.      * The byte array transformed into Unicode chars using hibyte
  158.      * as the upper byte of each character.
  159.      * @param ascii    the byte that will be converted to characters
  160.      * @param hibyte    the top 8 bits of each 16 bit Unicode character
  161.      */
  162.     public String(byte ascii[], int hibyte) {
  163.     this(ascii, hibyte, 0, ascii.length);
  164.     }
  165.  
  166.     /**
  167.      * Returns the length of the String.
  168.      * The length of the String is equal to the number of 16 bit
  169.      * Unicode characters in the String.
  170.      */
  171.     public int length() {
  172.     return count;
  173.     }
  174.  
  175.     /**
  176.      * Returns the character at the specified index. An index ranges
  177.      * from <tt>0</tt> to <tt>length() - 1</tt>.
  178.      * @param index    the index of the desired character
  179.      * @exception    StringIndexOutOfBoundsException If the index is not
  180.      *            in the range <tt>0</tt> to <tt>length()-1</tt>.
  181.      */
  182.     public char charAt(int index) {
  183.     if ((index < 0) || (index >= count)) {
  184.         throw new StringIndexOutOfBoundsException(index);
  185.     }
  186.     return value[index + offset];
  187.     }
  188.  
  189.     /**
  190.      * Copies characters from this String into the specified character array.
  191.      * The characters of the specified substring (determined by
  192.      * srcBegin and srcEnd) are copied into the character array,
  193.      * starting at the array's dstBegin location.
  194.      * @param srcBegin    index of the first character in the string
  195.      * @param srcEnd    end of the characters that are copied
  196.      * @param dst        the destination array
  197.      * @param dstBegin    the start offset in the destination array
  198.      */
  199.     public void getChars(int srcBegin, int srcEnd, char dst[], int dstBegin) {
  200.     System.arraycopy(value, offset + srcBegin, dst, dstBegin, srcEnd - srcBegin);
  201.     }
  202.  
  203.     /**
  204.      * Copies characters from this String into the specified byte array.
  205.      * Copies the characters of the specified substring (determined by
  206.      * srcBegin and srcEnd) into the byte array, starting at the
  207.      * array's dstBegin location.
  208.      * @param srcBegin    index of the first character in the String
  209.      * @param srcEnd    end of the characters that are copied
  210.      * @param dst        the destination array
  211.      * @param dstBegin    the start offset in the destination array
  212.      */
  213.     public void getBytes(int srcBegin, int srcEnd, byte dst[], int dstBegin) {
  214.     int j = dstBegin;
  215.     int n = offset + srcEnd;
  216.     int i = offset + srcBegin;
  217.     while (i < n) {
  218.         dst[j++] = (byte)value[i++];
  219.     }
  220.     }
  221.  
  222.     /**
  223.      * Compares this String to the specified object.
  224.      * Returns true if the object is equal to this String; that is,
  225.      * has the same length and the same characters in the same sequence.
  226.      * @param anObject    the object to compare this String against
  227.      * @return     true if the Strings are equal; false otherwise.
  228.      */
  229.     public boolean equals(Object anObject) {
  230.     if ((anObject != null) && (anObject instanceof String)) {
  231.         String anotherString = (String)anObject;
  232.         int n = count;
  233.         if (n == anotherString.count) {
  234.         char v1[] = value;
  235.         char v2[] = anotherString.value;;
  236.         int i = offset;
  237.         int j = anotherString.offset;
  238.         while (n-- != 0) {
  239.             if (v1[i++] != v2[j++]) {
  240.             return false;
  241.             }
  242.         }
  243.         return true;
  244.         }
  245.     }
  246.     return false;
  247.     }
  248.  
  249.     /**
  250.      * Compares this String to another object.
  251.      * Returns true if the object is equal to this String; that is,
  252.      * has the same length and the same characters in the same sequence.
  253.      * Upper case characters are folded to lower case before
  254.      * they are compared.
  255.      * @param anotherString    the String to compare this String against
  256.      * @return     true if the Strings are equal, ignoring case; false otherwise.
  257.      */
  258.     public boolean equalsIgnoreCase(String anotherString) {
  259.     return (anotherString != null) && (anotherString.count == count) &&
  260.         regionMatches(true, 0, anotherString, 0, count);
  261.     }
  262.  
  263.     /**
  264.      * Compares this String to another specified String.
  265.      * Returns an integer that is less than, equal to, or greater than zero.
  266.      * The integer's value depends on whether this String is less than, equal to, or greater
  267.      * than anotherString.
  268.      * @param anotherString the String to be compared
  269.      */
  270.     public int compareTo(String anotherString) {
  271.     int len1 = count;
  272.     int len2 = anotherString.count;
  273.     int n = Math.min(len1, len2);
  274.     char v1[] = value;
  275.     char v2[] = anotherString.value;
  276.     int i = offset;
  277.     int j = anotherString.offset;
  278.  
  279.     while (n-- != 0) {
  280.         char c1 = v1[i++];
  281.         char c2 = v2[j++];
  282.         if (c1 != c2) {
  283.         return c1 - c2;
  284.         }
  285.     }
  286.     return len1 - len2;
  287.     }
  288.  
  289.     /**
  290.      * Determines whether a region of this String matches the specified region
  291.      * of the specified String.
  292.      * @param toffset    where to start looking in this String
  293.      * @param other     the other String
  294.      * @param ooffset    where to start looking in the other String
  295.      * @param len       the number of characters to compare
  296.      * @return          true if the region matches with the other; false otherwise.
  297.      */
  298.     public boolean regionMatches(int toffset, String other, int ooffset, int len) {
  299.     char ta[] = value;
  300.     int to = offset + toffset;
  301.     int tlim = offset + count;
  302.     char pa[] = other.value;
  303.     int po = other.offset + ooffset;
  304.     int plim = po + other.count;
  305.     if ((ooffset < 0) || (toffset < 0) || (to + len > tlim) || (po + len > plim)) {
  306.         return false;
  307.     }
  308.     while (--len >= 0) {
  309.         if (ta[to++] != pa[po++]) {
  310.             return false;
  311.         }
  312.     }
  313.     return true;
  314.     }
  315.  
  316.     /**
  317.      * Determines whether a region of this String matches the specified region
  318.      * of the specified String.  If the boolean ignoreCase is true, upper case characters are 
  319.      * considered equivalent to lower case letters.
  320.      * @param ignoreCase if true, case is ignored
  321.      * @param toffset    where to start looking in this String
  322.      * @param other     the other String
  323.      * @param ooffset    where to start looking in the other String
  324.      * @param len       the number of characters to compare
  325.      * @return          true if the region matches with the other; false otherwise.
  326.      */
  327.     public boolean regionMatches(boolean ignoreCase,
  328.                          int toffset,
  329.                            String other, int ooffset, int len) {
  330.     char ta[] = value;
  331.     int to = offset + toffset;
  332.     int tlim = offset + count;
  333.     char pa[] = other.value;
  334.     char trt[] = Character.upCase;
  335.     int po = other.offset + ooffset;
  336.     int plim = po + other.count;
  337.     if ((ooffset < 0) || (toffset < 0) || (to + len > tlim) || (po + len > plim)) {
  338.         return false;
  339.     }
  340.     while (--len >= 0) {
  341.         int c1 = ta[to++];
  342.         int c2 = pa[po++];
  343.         if ((c1 != c2)
  344.             && (!ignoreCase ||
  345.             (c1 > 256) || (c2 > 256) ||
  346.             (trt[c1] != trt[c2]))) {
  347.         return false;
  348.         }
  349.     }
  350.     return true;
  351.     }
  352.  
  353.     /**
  354.      * Determines whether this String starts with some prefix.
  355.      * @param prefix    the prefix
  356.      * @param toffset    where to begin looking in the the String
  357.      * @return         true if the String starts with the specified prefix; false otherwise.
  358.      */
  359.     public boolean startsWith(String prefix, int toffset) {
  360.     char ta[] = value;
  361.     int to = offset + toffset;
  362.     int tlim = offset + count;
  363.     char pa[] = prefix.value;
  364.     int po = prefix.offset;
  365.     int pc = prefix.count;
  366.     int plim = po + pc;
  367.     if ((toffset < 0) || (to + pc > tlim)) {
  368.         return false;
  369.     }
  370.     while (--pc >= 0) {
  371.         if (ta[to++] != pa[po++]) {
  372.             return false;
  373.         }
  374.     }
  375.     return true;
  376.     }
  377.  
  378.     /**
  379.      * Determines whether this String starts with some prefix.
  380.      * @param prefix    the prefix
  381.      * @return         true if the String starts with the specified prefix; false otherwise. 
  382.      */
  383.     public boolean startsWith(String prefix) {
  384.     return startsWith(prefix, 0);
  385.     }
  386.  
  387.     /**
  388.      * Determines whether the String ends with some suffix.
  389.      * @param suffix    the suffix
  390.      * @return         true if the String ends with the specified suffix; false otherwise.
  391.      */
  392.     public boolean endsWith(String suffix) {
  393.     return startsWith(suffix, count - suffix.count);
  394.     }
  395.  
  396.     /**
  397.      * Returns a hashcode for this String. This is a large
  398.      * number composed of the character values in the String.
  399.      */
  400.     public int hashCode() {
  401.     int h = 0;
  402.     int off = offset;
  403.     char val[] = value;
  404.     int len = count;
  405.  
  406.     if (len < 16) {
  407.         for (int i = len ; i > 0; i--) {
  408.         h = (h * 37) + val[off++];
  409.         }
  410.     } else {
  411.         // only sample some characters
  412.         int skip = len / 8;
  413.         for (int i = len ; i > 0; i -= skip, off += skip) {
  414.         h = (h * 39) + val[off];
  415.         }
  416.     }
  417.     return h;
  418.     }
  419.  
  420.     /**
  421.      * Returns the index within this String of the first occurrence of the specified 
  422.      * character.  This method returns -1 if the index is not found.
  423.      * @param ch    the character to search for
  424.      */
  425.     public int indexOf(int ch) {
  426.     return indexOf(ch, 0);
  427.     }
  428.  
  429.     /**
  430.      * Returns the index within this String of the first occurrence of the specified 
  431.      * character, starting the search at fromIndex.  This method 
  432.      * returns -1 if the index is not found.
  433.      * @param ch    the character to search for
  434.      * @param fromIndex    the index to start the search from
  435.      */
  436.     public int indexOf(int ch, int fromIndex) {
  437.     int max = offset + count;
  438.     char v[] = value;
  439.  
  440.     for (int i = offset + fromIndex ; i < max ; i++) {
  441.         if (v[i] == ch) {
  442.         return i - offset;
  443.         }
  444.     }
  445.     return -1;
  446.     }
  447.  
  448.     /**
  449.      * Returns the index within this String of the last occurrence of the specified character.
  450.      * The String is searched backwards starting at the last character.
  451.      * This method returns -1 if the index is not found.
  452.      * @param ch    the character to search for
  453.      */
  454.     public int lastIndexOf(int ch) {
  455.     return lastIndexOf(ch, count - 1);
  456.     }
  457.  
  458.     /**
  459.      * Returns the index within this String of the last occurrence of the specified character.
  460.      * The String is searched backwards starting at fromIndex.
  461.      * This method returns -1 if the index is not found.
  462.      * @param ch    the character to search for
  463.      * @param fromIndex    the index to start the search from
  464.      */
  465.     public int lastIndexOf(int ch, int fromIndex) {
  466.     int min = offset;
  467.     char v[] = value;
  468.     
  469.     for (int i = offset + ((fromIndex >= count) ? count - 1 : fromIndex) ; i >= min ; i--) {
  470.         if (v[i] == ch) {
  471.         return i - offset;
  472.         }
  473.     }
  474.     return -1;
  475.     }
  476.  
  477.     /**
  478.      * Returns the index within this String of the first occurrence of the specified substring.
  479.      * This method returns -1 if the index is not found.
  480.      * @param str     the substring to search for
  481.      */
  482.     public int indexOf(String str) {
  483.     return indexOf(str, 0);
  484.     }
  485.  
  486.     /**
  487.      * Returns the index within this String of the first occurrence of the specified substring.
  488.      * The search is started at fromIndex.
  489.      * This method returns -1 if the index is not found.
  490.      * @param str     the substring to search for
  491.      * @param fromIndex    the index to start the search from
  492.      */
  493.     public int indexOf(String str, int fromIndex) {
  494.     char v1[] = value;
  495.     char v2[] = str.value;
  496.     int max = offset + (count - str.count);
  497.       test:
  498.     for (int i = offset + ((fromIndex < 0) ? 0 : fromIndex); i <= max ; i++) {
  499.         int n = str.count;
  500.         int j = i;
  501.         int k = str.offset;
  502.         while (n-- != 0) {
  503.         if (v1[j++] != v2[k++]) {
  504.             continue test;
  505.         }
  506.         }
  507.         return i - offset;
  508.     }
  509.     return -1;
  510.     }
  511.  
  512.     /**
  513.      * Returns the index within this String of the last occurrence of the specified substring.
  514.      * The String is searched backwards.
  515.      * This method returns -1 if the index is not found.
  516.      * @param str     the substring to search for
  517.      */
  518.     public int lastIndexOf(String str) {
  519.     return lastIndexOf(str, count - 1);
  520.     }
  521.  
  522.     /**
  523.      * Returns the index within this String of the last occurrence of the specified substring.
  524.      * The String is searched backwards starting at fromIndex.
  525.      * This method returns -1 if the index is not found.
  526.      * @param str     the substring to search for
  527.      * @param fromIndex    the index to start the search from
  528.      */
  529.     public int lastIndexOf(String str, int fromIndex) {
  530.     char v1[] = value;
  531.     char v2[] = str.value;
  532.     int min = offset;
  533.       test:
  534.     for (int i = offset + ((fromIndex >= count) ? count - 1 : fromIndex); i >= min ; i--) {
  535.         int n = str.count;
  536.         int j = i;
  537.         int k = str.offset;
  538.         while (n-- != 0) {
  539.         if (v1[j++] != v2[k++]) {
  540.             continue test;
  541.         }
  542.         }
  543.         return i - offset;
  544.     }
  545.     return -1;
  546.     }
  547.  
  548.     /**
  549.      * Returns the substring of this String. The substring is specified
  550.      * by a beginIndex (inclusive) and the end of the string.
  551.      * @param beginIndex the beginning index, inclusive
  552.      */
  553.     public String substring(int beginIndex) {
  554.     return substring(beginIndex, length());
  555.     }
  556.  
  557.     /**
  558.      * Returns the substring of a String. The substring is specified
  559.      * by a beginIndex (inclusive) and an endIndex (exclusive).
  560.      * @param beginIndex the beginning index, inclusive
  561.      * @param endIndex the ending index, exclusive
  562.      * @exception StringIndexOutOfBoundsException If the beginIndex or the endIndex is out 
  563.      * of range.
  564.      */
  565.     public String substring(int beginIndex, int endIndex) {
  566.     if (beginIndex > endIndex) {
  567.         int tmp = beginIndex;
  568.         beginIndex = endIndex;
  569.         endIndex = tmp;
  570.     }
  571.     if (beginIndex < 0) {
  572.         throw new StringIndexOutOfBoundsException(beginIndex);
  573.     } 
  574.     if (endIndex > count) {
  575.         throw new StringIndexOutOfBoundsException(endIndex);
  576.     }
  577.     return ((beginIndex == 0) && (endIndex == count)) ? this :
  578.            new String(value, offset + beginIndex, endIndex - beginIndex);
  579.     }
  580.  
  581.     /**
  582.      * Concatenates the specified string to the end of this String.
  583.      * @param str    the String which is concatenated to the end of this String
  584.      */
  585.     public String concat(String str) {
  586.     int otherLen = str.length();
  587.     if (otherLen == 0) {
  588.         return this;
  589.     }
  590.     char buf[] = new char[count + otherLen];
  591.     getChars(0, count, buf, 0);
  592.     str.getChars(0, otherLen, buf, count);
  593.     return new String(buf);
  594.     }
  595.  
  596.     /**
  597.      * Converts this String by replacing all occurences of oldChar with newChar.
  598.      * @param oldChar    the old character
  599.      * @param newChar    the new character
  600.      */
  601.     public String replace(char oldChar, char newChar) {
  602.     if (oldChar != newChar) {
  603.         int len = count;
  604.         int i = -1;
  605.         while (++i < len) {
  606.         if (value[offset + i] == oldChar) {
  607.             break;
  608.         }
  609.         }
  610.         if (i < len) {
  611.         char buf[] = new char[len];
  612.         for (int j = 0 ; j < i ; j++) {
  613.             buf[j] = value[offset+j];
  614.         }
  615.         while (i < len) {
  616.             char c = value[offset + i];
  617.             buf[i] = (c == oldChar) ? newChar : c;
  618.             i++;
  619.         }
  620.         return new String(buf);
  621.         }
  622.     }
  623.     return this;
  624.     }
  625.  
  626.     /**
  627.      * Converts all of the characters in this String to lower case.
  628.      * @return the String, converted to lowercase.
  629.      * @see Character#toLowerCase
  630.      * @see String#toUpperCase
  631.      */
  632.     public String toLowerCase() {
  633.     int len = count;
  634.     char trt[] = Character.downCase;
  635.     int i, c;
  636.     for (i = 0 ; i < len ; i++) {
  637.         c = value[offset+i];
  638.         if ((c < 256) && (trt[c] != c)) {
  639.         break;
  640.         }
  641.     }
  642.     if (i >= len) {
  643.         return this;
  644.     }
  645.     char buf[] = new char[len];
  646.     for (i = 0 ; i < len ; i++) {
  647.         c = value[offset+i];
  648.         buf[i] = (c < 256) ? trt[c] : (char)c;
  649.     }
  650.     return new String(buf);
  651.     }
  652.  
  653.     /**
  654.      * Converts all of the characters in this String to upper case.
  655.      * @return the String, converted to uppercase.
  656.      * @see Character#toUpperCase
  657.      * @see String#toLowerCase
  658.      */
  659.     public String toUpperCase() {
  660.     int len = count;
  661.     char trt[] = Character.upCase;
  662.     int i, c;
  663.     for (i = 0 ; i < len ; i++) {
  664.         c = value[offset+i];
  665.         if ((c < 256) && (trt[c] != c)) {
  666.         break;
  667.         }
  668.     }
  669.     if (i >= len) {
  670.         return this;
  671.     }
  672.     char buf[] = new char[len];
  673.     for (i = 0 ; i < len ; i++) {
  674.         c = value[offset+i];
  675.         buf[i] = (c < 256) ? trt[c] : (char)c;
  676.     }
  677.     return new String(buf);
  678.     }
  679.  
  680.     /**
  681.      * Trims leading and trailing whitespace from this String.
  682.      * @return the String, with whitespace removed.
  683.      */
  684.     public String trim() {
  685.     int len = count;
  686.     int st = 0;
  687.     while ((st < len) && (value[offset + st] <= ' ')) {
  688.         st++;
  689.     }
  690.     while ((st < len) && (value[offset + len - 1] <= ' ')) {
  691.         len--;
  692.     }
  693.     return ((st > 0) || (len < count)) ? substring(st, len) : this;
  694.     }
  695.  
  696.     /**
  697.      * Converts this String to a String.
  698.      * @return the String itself.
  699.      */
  700.     public String toString() {
  701.     return this;
  702.     }
  703.  
  704.     /**
  705.      * Converts this String to a character array. This creates a new array.
  706.      * @return     an array of characters.
  707.      */
  708.     public char[] toCharArray() {
  709.     int i, max = length();
  710.     char result[] = new char[max];
  711.     getChars(0, max, result, 0);
  712.     return result;
  713.     }
  714.  
  715.     /**
  716.      * Returns a String that represents the String value of the object.
  717.      * The object may choose how to represent itself by implementing
  718.      * the toString() method.
  719.      * @param obj    the object to be converted
  720.      */
  721.     public static String valueOf(Object obj) {
  722.     return (obj == null) ? "null" : obj.toString();
  723.     }
  724.  
  725.     /**
  726.      * Returns a String that is equivalent to the specified character array.
  727.      * Uses the original array as the body of the String (ie. it does not
  728.      * copy it to a new array).
  729.      * @param data    the character array
  730.      */
  731.     public static String valueOf(char data[]) {
  732.     return new String(data);
  733.     }
  734.  
  735.     /**
  736.      * Returns a String that is equivalent to the specified character array.
  737.      * Uses the original array as the body of the String (ie. it does not
  738.      * copy it to a new array).
  739.      * @param data    the character array
  740.      * @param offset    the offset into the value of the String
  741.      * @param count     the length of the value of the String
  742.      */
  743.     public static String valueOf(char data[], int offset, int count) {
  744.     return new String(data, offset, count);
  745.     }
  746.  
  747.     /**
  748.      * Returns a String that is equivalent to the specified character array.
  749.      * It creates a new array and copies the characters into it.
  750.      * @param data    the character array
  751.      * @param offset    the offset into the value of the String
  752.      * @param count     the length of the value of the String
  753.      */
  754.     public static String copyValueOf(char data[], int offset, int count) {
  755.     char str[] = new char[count];
  756.     System.arraycopy(data, offset, str, 0, count);
  757.     return new String(str);
  758.     }
  759.  
  760.     /**
  761.      * Returns a String that is equivalent to the specified character array.
  762.      * It creates a new array and copies the characters into it.
  763.      * @param data    the character array
  764.      */
  765.     public static String copyValueOf(char data[]) {
  766.     return copyValueOf(data, 0, data.length);
  767.     }
  768.  
  769.     /**
  770.      * Returns a String object that represents the state of the specified boolean.
  771.      * @param b    the boolean
  772.      */
  773.     public static String valueOf(boolean b) {
  774.     return b ? "true" : "false";
  775.     }
  776.  
  777.     /**
  778.      * Returns a String object that contains a single character
  779.      * @param c the character
  780.      * @return     the resulting String.
  781.      */
  782.     public static String valueOf(char c) {
  783.     char data[] = {c};
  784.     return new String(data);
  785.     }
  786.  
  787.     /**
  788.      * Returns a String object that represents the value of the specified integer.
  789.      * @param i    the integer
  790.      */
  791.     public static String valueOf(int i) {
  792.         return Integer.toString(i, 10);
  793.     }
  794.  
  795.     /**
  796.      * Returns a String object that represents the value of the specified long.
  797.      * @param l    the long
  798.      */
  799.     public static String valueOf(long l) {
  800.         return Long.toString(l, 10);
  801.     }
  802.  
  803.     /**
  804.      * Returns a String object that represents the value of the specified float.
  805.      * @param f    the float
  806.      */
  807.     public static String valueOf(float f) {
  808.     return float2String(f);
  809.     }
  810.  
  811.     /**
  812.      * Returns a String object that represents the value of the specified double.
  813.      * @param d    the double
  814.      */
  815.     public static String valueOf(double d) {
  816.     return double2String(d);
  817.     }
  818.  
  819.     /**
  820.      * The set of internalized Strings.
  821.      */
  822.     private static Hashtable InternSet;
  823.  
  824.     /**
  825.      * Returns a String that is equal to this String
  826.      * but which is guaranteed to be from the unique String pool.  For example:
  827.      * <pre>s1.intern() == s2.intern() <=> s1.equals(s2).</pre>
  828.      */
  829.     public String intern() {
  830.     if (InternSet == null) {
  831.         InternSet = new Hashtable();
  832.     }
  833.     String s = (String) InternSet.get(this);
  834.     if (s != null) {
  835.         return s;
  836.     }
  837.     InternSet.put(this, this);
  838.     return this;
  839.     }
  840.  
  841.     private static native String float2String(float f);
  842.     private static native String double2String(double d);
  843.  
  844.     /**
  845.      * Compute the length of this string's UTF encoded form.
  846.      */
  847.     int utfLength() {
  848.     int limit = offset + count;
  849.     int utflen = 0;
  850.     for (int i = offset; i < limit; i++) {
  851.         int c = value[i];
  852.         if ((c >= 0x0001) && (c <= 0x007F)) {
  853.         utflen++;
  854.         } else if (c > 0x07FF) {
  855.         utflen += 3;
  856.         } else {
  857.         utflen += 2;
  858.         }
  859.     }
  860.     return utflen;
  861.     }
  862. }
  863.